import gobject

from util import config
from db import db
from fvutil import fvcon
import time
import cPickle as pickle


class ObjectManager(gobject.GObject):
    
    def __init__(self, o_type, my_id, table=None):
        gobject.GObject.__init__(self)
        if table:
            self._table = table
        else:
            _db = db.get_database(config.get('fv', 'db-path'), config.get('fv', 'object-db'))
            self._table = _db.get_or_create(ObjectTable)
        self._type = o_type
        self._table._set_id(my_id)
        #self._path = self.__config.get('fv', ')
    
    def get(self, oid, do_map=True):
        obj = self._table.get(oid)
        if do_map:
            return self.to_flash(obj)
        else:
            return obj
    
    def get_all_of_type(self, type=None, do_map=True):
        if not type:
            type = self._type
        all_of_type = self._table.get_all_of_type(type)
        if do_map:
            return map(self.to_flash, all_of_type)
        else:
            return all_of_type
    
    def get_all(self, do_map=True):
        # TODO: This is a little bit weird; should think about whether this can be made clearer
        if self._type == fvcon.ALL:
            all = self._table.get_all()
            if do_map:
                return map(self.to_flash, all)
            else:
                return all
        else:
            return self.get_all_of_type(do_map=do_map)
    
    def add(self, obj_details):
        self._table.add(obj_details)
    
    def get_active(self, o_type=None,do_map=True):
        if not o_type:
            o_type = self._type
        if do_map:
            return map(self.to_flash, self._table.get_active(o_type))
        else:
            return self._table.get_active(o_type)
        
gobject.type_register(ObjectManager)

class ObjectTable(db.Table):
    
    def __init__(self):
        db.Table.__init__(self)
        
    def _set_id(self, my_id):
        self.__my_id = my_id
        
    def _init(self):
        self._conn.execute('''
            create table objects
            (oid INTEGER, type INTEGER, src INTEGER, dests STRING, 
            tags STRING, local_path STRING, created INTEGER, expires INTEGER, received INTEGER,
            meta STRING, sender BOOLEAN, header STRING, timestamp INTEGER)
            ''')
           
    def _drop(self):
        self._conn.execute('''
            drop table objects
            ''')
    
    def get(self, oid):
        c = self._conn
        rows = c.execute(''' SELECT header FROM objects WHERE oid=? ''', (oid,))
        result = None
        if rows:
            result = self.__db_to_py(rows[0]['header'])
        return result
    
    def get_all(self):
        c = self._conn
        rows = c.execute(''' SELECT header FROM objects ''')
        results = []
        for r in rows:
            r = self.__db_to_py(r['header'])
            results.append(r)
        return results
            
    
    def get_all_of_type(self, o_type):
        c = self._conn
        rows = c.execute(''' SELECT header FROM objects WHERE type=? ''', (o_type,))
        results = []
        for r in rows:
            r = self.__db_to_py(r['header'])
            results.append(r)
        return results
    
    def get_active(self,o_type):
        c = self._conn
        rows = c.execute(''' SELECT * FROM objects WHERE expires>? AND type=?''', (time.time(),o_type))
        results = []
        for r in rows:
            r = self.__db_to_py(r['header'])
            results.append(r)
        return results
    
    def __db_to_py(self, header):
        return pickle.loads(header.encode('ascii'))
    
    def __py_to_db(self, header):
        return pickle.dumps(header)
    
    def add(self, header):
        c = self._conn
        data = self.__py_to_db(header)
        c.execute(''' INSERT INTO objects VALUES(?,?,?,?,?,?,?,?,?,?,?,?, ?) ''', 
                  (header.mid,
                   header.msg_type,
                   header.src,
                   pickle.dumps(header.dests),
                   header.meta[fvcon.TAGS],
                   header.get_file_path(),
                   header.created,
                   header.expires,
                   header.received,
                   pickle.dumps(header.meta),
                   header.am_sender(self.__my_id),
                   pickle.dumps(header),
                   time.time()))
        
        
        
        
        